/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */

#include "rti-scheduler.h"
#include "event-impl.h"
#include "assert.h"
#include "log.h"
#include <string>

NS_LOG_COMPONENT_DEFINE ("RtiScheduler");

pthread_mutex_t WakeMutex;
pthread_cond_t WakeCond;

namespace ns3 {

NS_OBJECT_ENSURE_REGISTERED (RtiScheduler);

/*void *printHello(void *thID)
{
	int tid=0;
	tid = (long) thID;
        while(tid<10)
        {
 	NS_LOG_UNCOND("From Thread");
        tid++;
        }
	pthread_exit(NULL);
}*/

TypeId
RtiScheduler::GetTypeId (void)
{
  static TypeId tid = TypeId ("ns3::RtiScheduler")
    .SetParent<Scheduler> ()
    .AddConstructor<RtiScheduler> ()
  ;
  NS_LOG_UNCOND("Hello from RTI");
/*  pthread_t th;
  int r,i=0;
  r = pthread_create(&th,NULL,printHello, (void *)i); 
  if(r==1)
  {
        NS_LOG_UNCOND("yeah!!!");
  }*/
  //pthread_exit(NULL);	
  return tid;
}

RtiScheduler::RtiScheduler ()
{
}
RtiScheduler::~RtiScheduler ()
{
}

void
RtiScheduler::Insert (const Event &ev)
{
  NS_LOG_FUNCTION (this << ev.impl << ev.key.m_ts << ev.key.m_uid);
  std::pair<EventMapI,bool> result;
  result = m_list.insert (std::make_pair (ev.key, ev.impl));
  //NS_LOG_UNCOND(ev.key);
  //NS_LOG_UNCOND(ev.impl);
  NS_ASSERT (result.second);
}

bool
RtiScheduler::IsEmpty (void) const
{
  return m_list.empty ();
}

Scheduler::Event
RtiScheduler::PeekNext (void) const
{
  NS_LOG_FUNCTION (this);
  EventMapCI i = m_list.begin ();
  NS_ASSERT (i != m_list.end ());

  Event ev;
  ev.impl = i->second;
  ev.key = i->first;
  NS_LOG_DEBUG (this << ev.impl << ev.key.m_ts << ev.key.m_uid);
  return ev;
}
Scheduler::Event
RtiScheduler::RemoveNext (void)
{
  NS_LOG_FUNCTION (this);
  EventMapI i = m_list.begin ();
  NS_ASSERT (i != m_list.end ());
  Event ev;
  ev.impl = i->second;
  ev.key = i->first;
  m_list.erase (i);
  NS_LOG_DEBUG (this << ev.impl << ev.key.m_ts << ev.key.m_uid);
  return ev;
}

void
RtiScheduler::Remove (const Event &ev)
{
  NS_LOG_FUNCTION (this << ev.impl << ev.key.m_ts << ev.key.m_uid);
  EventMapI i = m_list.find (ev.key);
  NS_ASSERT (i->second == ev.impl);
  m_list.erase (i);
}

} // namespace ns3
